﻿using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using System.Threading.Tasks;
using OfficeOpenXml;
using OfficeOpenXml.Style;
using Volo.Abp;
using Volo.Abp.Application.Services;

namespace Colorful.Furniture.Epplus;

/// <summary>
///  excel导出
/// </summary>
public class ExcelExportAppService : ApplicationService
{
    /// <summary>
    ///   导出
    /// </summary>
    /// <returns></returns>
    [RemoteService(false)]
    public async Task<byte[]> ExportAsync<TExport>(List<TExport> exportEntities) where TExport : class
    {
        var entityExportAttribute = typeof(TExport).GetCustomAttribute<ExportAttribute>();

        var sheetName = entityExportAttribute != null ? entityExportAttribute.Title : "excel导出";

        using var package = new ExcelPackage();
        var worksheet = package.Workbook.Worksheets.Add(sheetName);

        var x = 1;
        var y = 1;

        var exportProperties = typeof(TExport).GetProperties().ToList();

        var exportAttributes = new List<ExportAttribute>();

        foreach (var property in exportProperties)
        {
            var exportAttribute = property.GetCustomAttribute<ExportAttribute>();

            if (exportAttribute != null)
            {
                if (exportAttribute.IsHide) continue;

                exportAttributes.Add(exportAttribute);
            }
            else
            {
                exportAttributes.Add(new ExportAttribute
                {
                    Title = property.Name,
                    IsHide = false
                });
            }
        }

        var columnIndex = 0;
        foreach (var exportAttribute in exportAttributes)
        {
            // 设置标题样式
            var cell = worksheet.Cells[x, y++];
            cell.Style.Font.Bold = true;
            worksheet.Row(1).Height = exportAttribute.Height;//设置行高
            worksheet.Column(columnIndex + 1).Width = exportAttribute.Width;//设置列宽
            cell.Style.HorizontalAlignment = exportAttribute.HorizontalAlignment;
            cell.Style.VerticalAlignment = exportAttribute.VerticalAlignment;
            cell.Value = exportAttribute.Title;
            cell.Style.Border.BorderAround(ExcelBorderStyle.Thin);

            columnIndex++;
        }

        foreach (var item in exportEntities)
        {
            x++;

            var properties = item.GetType().GetProperties();

            var exportAttribute = item.GetType().GetCustomAttribute<ExportAttribute>();

            var propertyColumnIndex = 1;

            foreach (var propertyInfo in properties)
            {
                var cell = worksheet.Cells[x, propertyColumnIndex];
                worksheet.Row(x).Height = exportAttribute?.Height ?? 30;//设置行高
                cell.Value = propertyInfo.GetValue(item, null);
                cell.Style.HorizontalAlignment = exportAttribute?.HorizontalAlignment ?? ExcelHorizontalAlignment.Center;
                cell.Style.VerticalAlignment = exportAttribute?.VerticalAlignment ?? ExcelVerticalAlignment.Center;
                cell.Style.Border.BorderAround(ExcelBorderStyle.Thin);
            }
        }

        return await Task.Run(() => package.GetAsByteArray());
    }
}